[Amazon SageMaker] CloudWatch Logsからaccuracyに関するスコアを取得して一覧してみました
1 はじめに
CX事業本部の平内(SIN)です。
Amazon SageMaker(以下、SageMaker)の組み込みアルゴリズム(イメージ分類)では、accuracyに関するメトリクスを自動で計算して発行しています。
そして、トレーニングの結果は、コンソールからグラフとして確認することもできます。
しかし、この機能は、トレーニングジョブ単位のため、増分学習などで、複数回に分けたジョブを俯瞰することは出来ません。また、グラフは時系列であり、epoch回数との関連を見ることは難しいと思います。
今回は、CloudWatch Logsから学習の進行の目安となる行を抜き出し、複数に分けたジョブも俯瞰できるようにしてみました。
以前、「物体検出アルゴリズム」用に書いた下記の「イメージ分類」版となります。
参考:[Amazon SageMaker] CloudWatch Logsからcross_entropyやmAPのスコアを取得して一覧してみました
2 CloudWatch Logs
SageMakerによるトレーニングのログでは、Epoch(ミニバッチ)ごとに、caccuracy の値がメトリックスとして出力されています。
ここで、caccuracyの上昇などは、モデルが十分に学習されているかどうかの目安になります。
以下は、CloudWatch Logsから"Epoch"という文字列でフィルタした出力例です。
Epoch[12] Batch [20]#011Speed: 227.297 samples/sec#011accuracy=0.879464 Epoch[12] Batch [40]#011Speed: 234.214 samples/sec#011accuracy=0.899390 Epoch[12] Batch [60]#011Speed: 233.078 samples/sec#011accuracy=0.896004 Epoch[12] Batch [80]#011Speed: 237.086 samples/sec#011accuracy=0.906636 Epoch[12] Train-accuracy=0.900735 Epoch[12] Time cost=11.420 Epoch[12] Validation-accuracy=0.931818 Epoch[13] Batch [20]#011Speed: 223.938 samples/sec#011accuracy=0.937500 Epoch[13] Batch [40]#011Speed: 223.945 samples/sec#011accuracy=0.926829 Epoch[13] Batch [60]#011Speed: 216.544 samples/sec#011accuracy=0.922131 Epoch[13] Batch [80]#011Speed: 224.821 samples/sec#011accuracy=0.931327 Epoch[13] Train-accuracy=0.924265 Epoch[13] Time cost=11.892 Epoch[13] Validation-accuracy=0.971726 Epoch[14] Batch [20]#011Speed: 223.023 samples/sec#011accuracy=0.949405 Epoch[14] Batch [40]#011Speed: 228.503 samples/sec#011accuracy=0.930640 Epoch[14] Batch [60]#011Speed: 230.378 samples/sec#011accuracy=0.939037 Epoch[14] Batch [80]#011Speed: 224.063 samples/sec#011accuracy=0.939429 Epoch[14] Train-accuracy=0.933088 Epoch[14] Time cost=11.973 Epoch[14] Validation-accuracy=0.991071
3 集計
上記のログを対象に、Train-accuracy及び、Validation-accuracyの数値を抜き出して、一覧にするコードです。 ジョブ名は、配列で指定するようになっており、複数回に分けてトレーニングしたログも纏めて処理できます。
from boto3.session import Session import re # Job名(複数指定可能) jobs = ['ic-Traning-001/algo-1-1589483525'] session = Session(profile_name='developer') client = session.client('logs') group_name = '/aws/sagemaker/TrainingJobs' # "Epoch" 及び "Early" が含まれるログ抽出する filter_pattern = "?Epoch ?Early" response = client.filter_log_events( logGroupName=group_name, logStreamNames=jobs, limit=1000, filterPattern=filter_pattern, ) # Train-accuracy, Validation-accuracy にそれぞれ振り分ける train = [] validation = [] early = '' for event in response["events"]: message = event["message"] if("Train-accuracy" in message): value = re.split('=', message)[1] # 視認しやすいように、少数第三位で丸める value = round(float(value), 3) train.append(value) if("Validation-accuracy" in message): value = re.split('=', message)[1] # 視認しやすいように、少数第三位で丸める value = round(float(value), 3) validation.append(value) if("criteria" in message): # Early stopping で停止した場合にログ出力する early = message[message.find('Early'):] # 表示 print("epoch\tTrain-accuracy\tValidation-accuracy") print("-----------------------------------------") for i in range(len(train)): print("{}\t{}\t{}".format(i, train[i], validation[i])) print(early)
出力結果です。ここで表示されているEpochは、ログが抽出したものではなく、単純に0からの連番になっているため、ストリームを複数指定したは、増分学習のログという前提です。 なお、早期に学習が止まった場合のログである、 "Early stopping criteria met." についても出力しています。
epoch Train-accuracy Validation-accuracy ----------------------------------------- 0 0.173 0.149 1 0.185 0.381 2 0.45 0.695 3 0.675 0.824 4 0.793 0.874 5 0.867 0.943 6 0.888 0.942 7 0.886 0.967 8 0.886 0.92 9 0.902 0.964 10 0.887 0.954 11 0.896 0.96 12 0.901 0.932 13 0.924 0.972 14 0.933 0.991 15 0.935 1.0 16 0.933 0.997 17 0.967 0.997 18 0.969 0.999 19 0.973 1.0 20 0.982 1.0 Early stopping criteria met.
4 最後に
今回は、複数に分けて行ったイメージ分類のトレーニング状況をEpochと共に俯瞰してみました。
一覧では、数値の桁数を丸めたりしていますが、このように、一定の形式で学習の進度を俯瞰することは有効なのではないかと考えています。